package com.itheima.service.impl;

import com.alibaba.dubbo.config.annotation.Service;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.itheima.dao.MenuDao;
import com.itheima.dao.RoleDao;
import com.itheima.dao.UserDao;

import com.itheima.entity.PageResult;
import com.itheima.entity.QueryPageBean;
import com.itheima.pojo.Menu;
import com.itheima.pojo.Role;
import com.itheima.pojo.User;
import com.itheima.service.MenuService;
import org.springframework.beans.factory.annotation.Autowired;

import java.util.*;

@Service(interfaceClass = MenuService.class)
public class MenuServiceImpl implements MenuService {


    @Autowired
    private MenuDao menuDao;

    /**
     * 分页查询
     *
     * @param queryPageBean
     * @return
     */
    @Override
    public PageResult findPage(QueryPageBean queryPageBean) {

        String queryString = queryPageBean.getQueryString();
        Integer currentPage = queryPageBean.getCurrentPage();
        Integer pageSize = queryPageBean.getPageSize();

        PageHelper.startPage(currentPage, pageSize);

        Page<Menu> page = menuDao.findPage(queryString);

        return new PageResult(page.getTotal(), page.getResult());
    }

    /**
     * 添加菜单
     * @param menu
     */
    @Override
    public void addMenu(Menu menu) {
        menuDao.addMenu(menu);
    }

    /**
     * 编辑菜单
     *
     * @param menu
     */
    @Override
    public void editMenu(Menu menu) {
        menuDao.editMenu(menu);
    }

    /**
     * 删除菜单
     * @param id
     */
    @Override
    public void deleteById(Integer id) {
        menuDao.deleteMenu(id);
    }

    /**
     * 回显编辑菜单
     * @param id
     * @return
     */
    @Override
    public Menu findById(Integer id) {
        return menuDao.findById(id);
    }


    /*感谢罗泽武提供的技术支持*/
    @Override
    public List<Menu> findListByUsername(String username) {
        User user = menuDao.findUser(username);
        if (user == null) {
            return null;
        }


        Set<Role> roleSet = menuDao.findRolesByUserId(user.getId());
            HashSet<Menu> menus = new HashSet<>();
            if (roleSet != null && roleSet.size() > 0) {
                for (Role role : roleSet) {
                    List<Menu> superMenus = menuDao.findMenuByRoleId(role.getId());
                    menus.addAll(superMenus);
                }

        }

        Integer count = 0;
        ArrayList<Menu> parents = new ArrayList<>();
        if (menus.size() > 0) {
            for (Menu menu : menus) {
                if (menu.getParentMenuId() == null) {
                    parents.add(menu);
                    count++;
                }
            }
        }
        //对菜单排序
        orderByPriority(parents);
        //找寻子级菜单
        queryChildren(count, menus, parents);
        return parents;
    }


    /**
     * 查询子菜单
     *
     * @param count
     * @param menus
     * @param parents
     */
    private void queryChildren(Integer count, HashSet<Menu> menus, List<Menu> parents) {
        if (parents != null && parents.size() > 0) {
            for (Menu parent : parents) {
                ArrayList<Menu> children = new ArrayList<>();
                for (Menu menu : menus) {
                    if (menu.getParentMenuId() != null && menu.getParentMenuId().equals(parent.getId())) {
                        //说明找到此父菜单的子菜单
                        children.add(menu);
                        count++;
                    }
                }
                orderByPriority(children);
                parent.setChildren(children);
            }
            //条件满足表示尚未匹配完成，需要继续递归
            if (count < menus.size()) {
                for (Menu parent : parents) {
                    List<Menu> children = parent.getChildren();
                    this.queryChildren(count, menus, children);
                }
            }
        }

    }

    /**
     * 对菜单进行排序
     *
     * @param menus
     */
    private void orderByPriority(List<Menu> menus) {
        //排序法：每次循环比较出最小，放在前面
        for (int i = 0; i < menus.size(); i++) {
            int index = i;
            for (int j = i; j < menus.size(); j++) {
                //根据最小的索引，获取最小的元素
                Menu min = menus.get(index);
                //获取当前遍历的元素
                Menu menu = menus.get(j);
                //比较两元素的大小
                if (menu.getPriority() < min.getPriority()) {
                    //当前元素小于最小min:跟新最小元素index
                    index = j;
                }
            }
            //换位
            Menu min = menus.get(index);
            Menu first = menus.get(i);
            menus.set(i, min);
            menus.set(index, first);
        }
    }

}